package com.chaos.framework.starter.base;


import cn.hutool.core.util.IdUtil;
import cn.hutool.core.util.ObjectUtil;
import cn.hutool.json.JSONUtil;
import com.chaos.framework.model.constant.Constants;
import com.chaos.framework.model.dto.DTO;
import com.chaos.framework.model.dto.ID;
import com.chaos.framework.model.dto.MU;
import com.chaos.framework.model.dto.page.PageList;
import com.chaos.framework.model.dto.result.data.BooleanResult;
import com.chaos.framework.model.dto.result.data.DataResult;
import com.chaos.framework.model.dto.result.data.StringResult;
import com.chaos.framework.model.dto.result.list.ListResult;
import com.chaos.framework.model.dto.result.page.PageResult;
import com.chaos.framework.model.enums.ResultEnum;
import com.chaos.framework.model.exception.BusinessException;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang3.StringUtils;
import org.slf4j.MDC;

import jakarta.annotation.Resource;
import jakarta.servlet.http.HttpServletRequest;
import jakarta.servlet.http.HttpServletResponse;

import java.util.List;

/**
 * @author Jacky
 */
@Slf4j
public abstract class BaseController<T extends DTO> {
    @Resource
    protected HttpServletRequest request;
    @Resource
    protected HttpServletResponse response;


    public DataResult<T> ok(T data) {
        return DataResult.ok(data);
    }

    public DataResult<T> error(ResultEnum resultEnum) {
        return DataResult.error(resultEnum);
    }

    public DataResult<T> error(Integer errorCode, String msg) {
        return DataResult.error(errorCode, msg);
    }

    public DataResult<T> error(Integer errorCode, String msg, T data) {
        return DataResult.error(errorCode, msg, data);
    }

    public BooleanResult booleanResult(Boolean data) {
        return BooleanResult.ok(data);
    }

    public StringResult stringResult(String data) {
        return StringResult.ok(data);
    }

    public DataResult<T> dataResult(T data) {
        return DataResult.ok(data);
    }

    public DataResult<ID> dataResult(ID id) {
        return new DataResult<>(ResultEnum.OK.getCode(), ResultEnum.OK.getMsg(), id);
    }

    public DataResult<MU> dataResult(MU mu) {
        return new DataResult<>(ResultEnum.OK.getCode(), ResultEnum.OK.getMsg(), mu);
    }

    public DataResult<Boolean> dataResult(Boolean data) {
        return new DataResult<>(ResultEnum.OK.getCode(), ResultEnum.OK.getMsg(), data);
    }

    public DataResult<String> dataResult(String data) {
        return new DataResult<>(ResultEnum.OK.getCode(), ResultEnum.OK.getMsg(), data);
    }

    public DataResult<Integer> dataResult(Integer data) {
        return new DataResult<>(ResultEnum.OK.getCode(), ResultEnum.OK.getMsg(), data);
    }

    public DataResult<Double> dataResult(Double data) {
        return new DataResult<>(ResultEnum.OK.getCode(), ResultEnum.OK.getMsg(), data);
    }

    public DataResult<Float> dataResult(Float data) {
        return new DataResult<>(ResultEnum.OK.getCode(), ResultEnum.OK.getMsg(), data);
    }

    public DataResult<List<T>> dataResult(List<T> data) {
        return new DataResult<>(ResultEnum.OK.getCode(), ResultEnum.OK.getMsg(), data);
    }

    public ListResult<T> listResult(List<T> list) {
        return ListResult.ok(list);
    }

    public PageResult<T> pageResult(PageList<T> pageList) {
        return PageResult.ok(pageList);
    }

    // userId 是登录凭证
    public Long getUserIdNotNull() {
        String userId = request.getHeader("X-User-Id");
        if (ObjectUtil.isEmpty(userId)) {
            throw new BusinessException(ResultEnum.NO_USER_ID);
        }
        return Long.valueOf(userId);
    }

    /**
     * @return userInfoId（同一手机号唯一 id）
     */
    public Long getUserInfoId() {
        String userInfoId = request.getHeader("X-User-Info-Id");
        if (ObjectUtil.isEmpty(userInfoId)) {
            return null;
        }
        return Long.valueOf(userInfoId);
    }

    public Long getUserInfoIdNotNull() {
        String userInfoId = request.getHeader("X-User-Info-Id");
        if (ObjectUtil.isEmpty(userInfoId)) {
            throw new BusinessException(ResultEnum.NO_USER_INFO_ID);
        }
        return Long.valueOf(userInfoId);
    }

    public Long getAdminId() {
        String adminId = request.getHeader("X-Admin-Id");
        if (ObjectUtil.isEmpty(adminId)) {
            return null;
        }
        return Long.valueOf(adminId);
    }

    public Long getAdminIdNotNull() {
        String adminId = request.getHeader("X-Admin-Id");
        if (ObjectUtil.isEmpty(adminId)) {
            throw new BusinessException(ResultEnum.NO_ADMIN_ID);
        }
        return Long.valueOf(adminId);
    }

    public Long getTenantId() {
        return Long.valueOf(request.getHeader("X-Tenant-Id"));
    }

    public Long getClientId() {
        return Long.valueOf(request.getHeader("X-Client-Id"));
    }

    public String getTraceId() {
        String traceId = request.getHeader(Constants.TRACE_ID);
        if (ObjectUtil.isEmpty(traceId)) {
            traceId = IdUtil.simpleUUID();
            MDC.put(Constants.TRACE_ID, traceId);
        }
        return traceId;
    }

    public String json(Object data) {
        return JSONUtil.toJsonStr(data);
    }


}
